#ifndef WORKSPACE_H_
#define WORKSPACE_H_

#include <gtkmm/drawingarea.h>
#include <gtkmm/printcontext.h>
#include <gtkmm/printoperation.h>
#include <iostream>
#include <vector>
#include <map>
#include <list>
#include "../Dibujar/Defines.h"
#include "../Dibujar/AuxiliarDibujar.h"
#include "../../model/Diagram.h"
#include "DrawingAreaPlusPlus.h"
#include "gui/VisualComponents/der/VisualComponentEntity.h"
#include <fstream>
#include <iostream>

class Tabs;

class Workspace : public DrawingAreaPlusPlus {
protected:
	Diagram* m_diagram;
	int m_diagramOffsetX;
	int m_diagramOffsetY;
	bool _necesitaReacomodar;

	Glib::RefPtr<Gtk::PageSetup> m_refPageSetup;
	Glib::RefPtr<Gtk::PrintSettings> m_refSettings;

public:
	Workspace(Diagram* diagram, bool enableEvents = true);
	virtual ~Workspace();


	/*Funciones y metodos que se mantienen para ambos diagramas:*/
	void imprimirAPng(std::string archivo);
	void imprimirAPdf(std::string archivo);
	void print_or_preview(Glib::RefPtr<Gtk::PrintOperation> print);
	void on_menu_file_page_setup();
	void on_menu_file_print_preview();
	void on_menu_file_print();
	void on_draw_page(const Glib::RefPtr< Gtk::PrintContext >& context, int page_nr);

    void updateDiagramSize();
    void getSize(double& sizeX, double& sizeY);
    void getPageSize(double& sizeX, double& sizeY);

	/*Funciones y metodos que quedan igual pero pueden llegar a cambiar*/
	Diagram* getDiagram();
    VisualDiagramComponent* getVisualComponent(Component*);
    VisualDiagramComponent* getVisualComponent(unsigned id);


    /*Funciones y metodos que dependen del tipo de diagrama*/
    virtual void validateDiagram(std::string archivo)=0;
    virtual void on_load(XmlReader& reader, Tabs* tabs)=0;
    virtual void on_load(XmlReader& readerModel, XmlReader & readerRep, Tabs* tabs)=0;
    virtual void store(XmlWriter& writer_rep, XmlWriter& writer_comp)=0;
    virtual void store(XmlWriter& writer_rep, XmlWriter& writer_comp, std::string tabName)=0;

    void necesitaReacomodar() {
    	_necesitaReacomodar = true;
    }

    virtual bool on_expose_event(GdkEventExpose* event) {
    	prepareScreenContext(get_window()->create_cairo_context());
//    	if (_necesitaReacomodar) {
//    		bool aunSePisan = alejarComponentesParaQueNoSePisen();
//    		if (aunSePisan) {
//    			on_expose_event(event);
//    		} else {
//    			_necesitaReacomodar = false;
//    		}
//    	}
    	return true;
    }

protected:
    // retorna verdadero si hubo colisiones
    bool alejarComponentesParaQueNoSePisen();
};

#endif /* WORKSPACE_H_ */
